/*
 * lower_ir.h
 *
 * Implements a lower-level IR. This is an IR that captures more
 * closely the information needed to produce code for a machine. It
 * contains maintainance of stack pointers, frame pointers, return
 * addresses, system registers, etc.
 */


#ifndef LIR_H
#define LIR_H



#include "ir.h"

struct mc_t { // MIPS code entry
	enum { // Types of instruction
		MIPS_ADD, MIPS_ADD_I,
		MIPS_AND, MIPS_AND_I,
		MIPS_BEQ, MIPS_BNE, MIPS_DIV, MIPS_JUMP, MIPS_JUMP_LINK, MIPS_LOAD_ADD, MIPS_LOAD_WORD, MIPS_LOAD_IMM, MIPS_MFLO, MIPS_MFLH, MIPS_MULT,
		MIPS_LABEL, MIPS_OR, MIPS_OR_I, MIPS_SET_LESS_THAN, MIPS_SET_LESS_THAN_I,
		MIPS_SHIFT_LEFT, MIPS_SHIFT_RIGHT,
		MIPS_STORE_WORD, MIPS_SUBTRACT, MIPS_BRANCH, MIPS_XOR
	} opcode;
	// Operands
	char *rs;
	char *rt;
	char *rd;
	int  imm;		// immediate
	char *label;	// for jump label
	struct mc_t *next;
};

struct lir_t { // Intermediate representation
	char *lid;
	struct mc_t *instruction;

	struct lir_t *next; // Next source block

	char *lcond; // Condition on which to branch
	struct lir_t *child; // Next execution block (also no branch of condition)
	struct lir_t *otherChild; // Yes branch of condition

	struct lir_t *parent; // First parent
	struct lir_t *nextParent; // Next parent at same level

	int numbered; // Has it been value-numbered?
	struct mc_t *stack; // Local value-numbering stack
};

struct lir_list_t {
	struct lir_t *lir;
	struct lir_list_t *next;
};

struct lir_list_t *global_lir_list;

// Functions
struct lir_t * lir_map_ir(struct ir_t *ir);
void add_to_global_lir_list(struct lir_t *lir);
struct lir_list_t *global_lir_list_init();

#endif /* LIR_H */
